package org.linlinjava.litemall.db.service;

import com.github.pagehelper.PageHelper;
import org.apache.commons.lang.StringUtils;
import org.linlinjava.litemall.db.dao.LitemallCategoryMapper;
import org.linlinjava.litemall.db.dao.LitemallGoodsMapper;
import org.linlinjava.litemall.db.dao.app.AppGoodsMapper;
import org.linlinjava.litemall.db.domain.LitemallGoods;
import org.linlinjava.litemall.db.domain.LitemallGoods.Column;
import org.linlinjava.litemall.db.domain.LitemallGoodsExample;
import org.linlinjava.litemall.db.util.GoodsConstant;
import org.linlinjava.litemall.db.vo.app.AgedmallPartsVo;
import org.linlinjava.litemall.db.vo.app.HomeGoodsListVo;
import org.linlinjava.litemall.db.vo.app.StoreGoodsVo;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import org.springframework.web.bind.annotation.RequestMapping;

import javax.annotation.Resource;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

import static org.linlinjava.litemall.db.util.GlobalConstantData.ALL_CITY;
import static org.linlinjava.litemall.db.util.GlobalConstantData.ALL_PROVINCE;

@Service
public class LitemallGoodsService {
    Column[] columns = new Column[]{Column.id, Column.name, Column.brief, Column.picUrl, Column.isHot, Column.isNew, Column.counterPrice, Column.retailPrice, Column.deposit, Column.categoryId, Column.isOnSale, Column.unit, Column.tags, Column.goodsType, Column.city};
    @Resource
    private LitemallGoodsMapper goodsMapper;
    @Resource
    private LitemallCategoryMapper categoryMapper;
    @Resource
    private AppGoodsMapper appGoodsMapper;

    /**
     * 获取热卖商品
     *
     * @param offset
     * @param limit
     * @return
     */
    public List<LitemallGoods> queryByHot(int offset, int limit) {
        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andIsHotEqualTo(true).andIsOnSaleEqualTo(true).andDeletedEqualTo(false);
        example.setOrderByClause("add_time desc");

        PageHelper.startPage(offset, limit);

        return goodsMapper.selectByExampleSelective(example, columns);
    }

    /**
     * 获取新品上市
     *
     * @param offset
     * @param limit
     * @return
     */
    public List<LitemallGoods> queryByNew(int offset, int limit) {
        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andIsNewEqualTo(true).andIsOnSaleEqualTo(true).andDeletedEqualTo(false);
        example.setOrderByClause("add_time desc");
        PageHelper.startPage(offset, limit);

        return goodsMapper.selectByExampleSelective(example, columns);
    }

    /**
     * 获取分类下的商品
     *
     * @param catList
     * @param offset
     * @param limit
     * @return
     */
    public List<LitemallGoods> queryByCategory(List<Integer> catList, int offset, int limit) {
        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andCategoryIdIn(catList).andIsOnSaleEqualTo(true).andDeletedEqualTo(false);
        example.setOrderByClause("add_time  desc");
        PageHelper.startPage(offset, limit);

        return goodsMapper.selectByExampleSelective(example, columns);
    }


    /**
     * 获取分类下的商品
     *
     * @param catId
     * @param offset
     * @param limit
     * @return
     */
    public List<LitemallGoods> queryByCategory(Integer catId, int offset, int limit) {
        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andCategoryIdEqualTo(catId).andIsOnSaleEqualTo(true).andDeletedEqualTo(false);
        example.setOrderByClause("add_time desc");
        PageHelper.startPage(offset, limit);

        return goodsMapper.selectByExampleSelective(example, columns);
    }

    public List<Integer> queryList(String province, String city, Integer storeId, Integer catId, String goodsType, Integer brandId,
                                   String keywords, Boolean isHot, Boolean isNew, Integer offset, Integer limit, String sort, String order,
                                   List<Integer> hospitalGoodsList) {
        PageHelper.startPage(offset, limit);
        Integer hot = null == isHot ? null : (isHot ? 1 : 0);
        Integer n1w = null == isNew ? null : (isNew ? 1 : 0);
        return appGoodsMapper.list(province, city, storeId, catId, goodsType, brandId, keywords, hot, n1w, sort, order,
                hospitalGoodsList!=null&&hospitalGoodsList.size()>0?hospitalGoodsList:null);
    }

    public List<LitemallGoods> querySelective(String province, String city, Integer storeId, Integer catId, String goodsType, Integer brandId, String keywords, Boolean isHot, Boolean isNew, Integer offset, Integer limit, String sort, String order) {
        LitemallGoodsExample example = new LitemallGoodsExample();
        LitemallGoodsExample.Criteria criteria1 = example.or();
        LitemallGoodsExample.Criteria criteria2 = example.or();

        if(StringUtils.isNotBlank(city)) {
            if(!ALL_PROVINCE.equals(province)) {
                List<String> provinces = new ArrayList<>();
                provinces.add(ALL_PROVINCE);
                provinces.add(province);
                criteria1.andProvinceIn(provinces);
                criteria2.andProvinceIn(provinces);
            }else {
                criteria1.andProvinceEqualTo(province);
                criteria2.andProvinceEqualTo(province);
            }
        }
        if(StringUtils.isNotBlank(city)) {
            if(!ALL_CITY.equals(city)) {
                List<String> citys = new ArrayList<>();
                citys.add(ALL_CITY);
                citys.add(city);
                criteria1.andCityIn(citys);
                criteria2.andCityIn(citys);
            }else {
                criteria1.andCityEqualTo(city);
                criteria2.andCityEqualTo(city);
            }
        }
        if(storeId != null && storeId != 0) {
            criteria1.andStoreIdEqualTo(storeId);
            criteria2.andStoreIdEqualTo(storeId);
        }
        if (catId != null && catId != 0) {
            criteria1.andCategoryIdEqualTo(catId);
            criteria2.andCategoryIdEqualTo(catId);
        }
        if(StringUtils.isNotBlank(goodsType)) {
            criteria1.andGoodsTypeEqualTo(goodsType);
            criteria2.andGoodsTypeEqualTo(goodsType);
        }
        if (brandId != null) {
            criteria1.andBrandIdEqualTo(brandId);
            criteria2.andBrandIdEqualTo(brandId);
        }
        if (isNew != null) {
            criteria1.andIsNewEqualTo(isNew);
            criteria2.andIsNewEqualTo(isNew);
        }
        if (isHot != null) {
            criteria1.andIsHotEqualTo(isHot);
            criteria2.andIsHotEqualTo(isHot);
        }
        if (!StringUtils.isEmpty(keywords)) {
            criteria1.andKeywordsLike("%" + keywords + "%");
            criteria2.andNameLike("%" + keywords + "%");
        }
//        criteria1.andIsOnSaleEqualTo(true);
//        criteria2.andIsOnSaleEqualTo(true);
        criteria1.andDeletedEqualTo(false);
        criteria2.andDeletedEqualTo(false);

        if (!StringUtils.isEmpty(sort) && !StringUtils.isEmpty(order)) {
            example.setOrderByClause(sort + " " + order);
        }

        PageHelper.startPage(offset, limit);

        return goodsMapper.selectByExampleSelective(example, columns);
    }

    public List<LitemallGoods> querySelective(Integer goodsId, String goodsSn, String name, Integer page, Integer size, String sort, String order) {
        LitemallGoodsExample example = new LitemallGoodsExample();
        LitemallGoodsExample.Criteria criteria = example.createCriteria();

        if (goodsId != null) {
            criteria.andIdEqualTo(goodsId);
        }
        if (!StringUtils.isEmpty(goodsSn)) {
            criteria.andGoodsSnEqualTo(goodsSn);
        }
        if (!StringUtils.isEmpty(name)) {
            criteria.andNameLike("%" + name + "%");
        }
        criteria.andDeletedEqualTo(false);

        if (!StringUtils.isEmpty(sort) && !StringUtils.isEmpty(order)) {
            example.setOrderByClause(sort + " " + order);
        }

        PageHelper.startPage(page, size);
        return goodsMapper.selectByExampleWithBLOBs(example);
    }

    /**
     * 获取某个商品信息,包含完整信息
     *
     * @param id
     * @return
     */
    public LitemallGoods findById(Integer id) {
        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andIdEqualTo(id).andDeletedEqualTo(false);
        return goodsMapper.selectOneByExampleWithBLOBs(example);
    }

    /**
     * 获取某个商品信息，仅展示相关内容
     *
     * @param id
     * @return
     */
    public LitemallGoods findByIdVO(Integer id) {
        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andIdEqualTo(id).andIsOnSaleEqualTo(true).andDeletedEqualTo(false);
        return goodsMapper.selectOneByExampleSelective(example, columns);
    }


    /**
     * 获取所有在售物品总数
     *
     * @return
     */
    public Integer queryOnSale() {
        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andIsOnSaleEqualTo(true).andDeletedEqualTo(false);
        return (int) goodsMapper.countByExample(example);
    }

    public int updateById(LitemallGoods goods) {
        goods.setUpdateTime(LocalDateTime.now());
        return goodsMapper.updateByPrimaryKeySelective(goods);
    }

    public void deleteById(Integer id) {
        goodsMapper.logicalDeleteByPrimaryKey(id);
    }

    public void add(LitemallGoods goods) {
        goods.setAddTime(LocalDateTime.now());
        goods.setUpdateTime(LocalDateTime.now());
        goodsMapper.insertSelective(goods);
    }

    /**
     * 获取所有物品总数，包括在售的和下架的，但是不包括已删除的商品
     *
     * @return
     */
    public int count() {
        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andDeletedEqualTo(false);
        return (int) goodsMapper.countByExample(example);
    }

    public List<Integer> getCatIds(Integer brandId, String keywords, Boolean isHot, Boolean isNew) {
        LitemallGoodsExample example = new LitemallGoodsExample();
        LitemallGoodsExample.Criteria criteria1 = example.or();
        LitemallGoodsExample.Criteria criteria2 = example.or();

        if (brandId != null) {
            criteria1.andBrandIdEqualTo(brandId);
            criteria2.andBrandIdEqualTo(brandId);
        }
        if (isNew != null) {
            criteria1.andIsNewEqualTo(isNew);
            criteria2.andIsNewEqualTo(isNew);
        }
        if (isHot != null) {
            criteria1.andIsHotEqualTo(isHot);
            criteria2.andIsHotEqualTo(isHot);
        }
        if (!StringUtils.isEmpty(keywords)) {
            criteria1.andKeywordsLike("%" + keywords + "%");
            criteria2.andNameLike("%" + keywords + "%");
        }
        criteria1.andIsOnSaleEqualTo(true);
        criteria2.andIsOnSaleEqualTo(true);
        criteria1.andDeletedEqualTo(false);
        criteria2.andDeletedEqualTo(false);

        List<LitemallGoods> goodsList = goodsMapper.selectByExampleSelective(example, Column.categoryId);
        List<Integer> cats = new ArrayList<Integer>();
        for (LitemallGoods goods : goodsList) {
            cats.add(goods.getCategoryId());
        }
        return cats;
    }

    public boolean checkExistByName(String name) {
        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andNameEqualTo(name).andIsOnSaleEqualTo(true).andDeletedEqualTo(false);
        return goodsMapper.countByExample(example) != 0;
    }

    public List<LitemallGoods> queryByIds(Integer ids) {
        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andIdIn(Arrays.asList(ids)).andIsOnSaleEqualTo(true).andDeletedEqualTo(false);
        return goodsMapper.selectByExampleSelective(example, columns);
    }

    /**
     * 获取门店下指定类型上架商品数
     * @param storeId
     * @param goodsType
     * @return
     */
    public int countByStoreId(Integer storeId, String goodsType) {
        return appGoodsMapper.getCountByStoreId(storeId, goodsType);
    }

    public int countByStoreId(Integer storeId, String goodsType, String province, String city) {
        return appGoodsMapper.getCountByStoreIdAndLocation(storeId, goodsType, province, city);
    }

    public List<StoreGoodsVo> queryCartRecommendList(String province, String city, int offset, int limit) {
        PageHelper.startPage(offset, limit);
        return appGoodsMapper.queryCartRecommendList(province, city);
    }

    public int countCartRecommendList(String province, String city) {
        return appGoodsMapper.countCartRecommendList(province, city);
    }

    public List<StoreGoodsVo> queryByIdList(List<Integer> idList) {
        return appGoodsMapper.queryByIdList(idList);
    }

    public List<StoreGoodsVo> queryByGoodsIdList(List<Integer> idList) {
        return appGoodsMapper.queryByGoodsIdList(idList);
    }

    public List<StoreGoodsVo> queryCustomList(String province, String city, Integer page, Integer limit) {
        PageHelper.startPage(page, limit);
        return appGoodsMapper.queryCustomList(province, city);
    }

    public List<LitemallGoods> queryDeductList(String province, String city, Integer page, Integer limit) {
        List<String> provinces = new ArrayList<>();
        provinces.add(ALL_PROVINCE);
        provinces.add(province);
        List<String> citys = new ArrayList<>();
        citys.add(ALL_CITY);
        citys.add(city);

        PageHelper.startPage(page, limit);

        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andDeletedEqualTo(false)
                .andGoodsTypeEqualTo(GoodsConstant.GOODS_TYPE_LEASE)
                .andUseDeductEqualTo(true)
                .andProvinceIn(provinces)
                .andCityIn(citys);
        return goodsMapper.selectByExample(example);
    }

    public int queryDeductListCount(String province, String city) {
        List<String> provinces = new ArrayList<>();
        provinces.add(ALL_PROVINCE);
        provinces.add(province);
        List<String> citys = new ArrayList<>();
        citys.add(ALL_CITY);
        citys.add(city);

        LitemallGoodsExample example = new LitemallGoodsExample();
        example.or().andDeletedEqualTo(false)
                .andGoodsTypeEqualTo(GoodsConstant.GOODS_TYPE_LEASE)
                .andUseDeductEqualTo(true)
                .andProvinceIn(provinces)
                .andCityIn(citys);
        Long count = goodsMapper.countByExample(example);
        return count.intValue();
    }

    public List<AgedmallPartsVo> queryParts(Integer specInfoId, Integer storeId) {
        return appGoodsMapper.queryParts(specInfoId, storeId);
    }

    public List<AgedmallPartsVo> queryPartsList(List<Integer> specIdList, List<Integer> storeIdList) {
        if(specIdList == null || specIdList.size() == 0 || storeIdList == null || storeIdList.size() == 0) {
            return new ArrayList<>();
        }
        return appGoodsMapper.queryPartsList(specIdList, storeIdList);
    }

    public List<AgedmallPartsVo> queryServices(Integer specInfoId) {
        return appGoodsMapper.queryServices(specInfoId);
    }

    public List<AgedmallPartsVo> queryServicesList(List<Integer> specIdList) {
        if(specIdList == null || specIdList.size() == 0) {
            return new ArrayList<>();
        }
        return appGoodsMapper.queryServicesList(specIdList);
    }

    public List<HomeGoodsListVo> queryHomeGoodsList(Integer categoryId, Integer subCategoryId, String type, String searchKey, Integer offset, Integer limit) {
        PageHelper.startPage(offset, limit);
        return appGoodsMapper.homeGoodsList(categoryId, subCategoryId, type, searchKey);
    }
}
